package com.eian.boot.common.core.utils;

import jakarta.servlet.http.HttpServletRequest;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
import org.springframework.util.StringUtils;

/**
 * IP工具类
 *
 * @author alex.meng
 */
@NoArgsConstructor(access = AccessLevel.PRIVATE)
public final class IpUtils {
    private static final String UNKNOWN = "unknown";
    private static final String[] IP_HEADER_CANDIDATES = {
            "X-Forwarded-For",
            "Proxy-Client-IP",
            "WL-Proxy-Client-IP"
    };

    /**
     * 获取请求的IP地址
     *
     * @param request 请求信息
     * @return IP地址
     */
    public static String getClientIp(HttpServletRequest request) {
        for (String header : IP_HEADER_CANDIDATES) {
            String ip = getIpFromHeader(request, header);
            if (ip != null) {
                return ip;
            }
        }

        return request.getRemoteAddr();
    }

    /**
     * 从请求头中获取IP地址
     *
     * @param request 请求信息
     * @param header  请求头名称
     * @return IP地址，如果无效则返回null
     */
    private static String getIpFromHeader(HttpServletRequest request, String header) {
        String ip = request.getHeader(header);
        if (ip != null && !ip.isEmpty() && !UNKNOWN.equalsIgnoreCase(ip)) {
            // 如果有多个代理服务器，X-Forwarded-For会包含多个IP，取第一个即为真实IP
            if (ip.contains(",")) {
                ip = ip.split(",")[0].trim();
            }
            return ip;
        }
        return null;
    }

    /**
     * 检查IP是否未知
     *
     * @param ip IP地址
     * @return 是否未知
     */
    private static boolean isUnknown(String ip) {
        return !StringUtils.hasText(ip) || UNKNOWN.equalsIgnoreCase(ip);
    }
}

